﻿using System;
using System.ComponentModel;
using System.Windows;
using System.Windows.Interactivity;


namespace DailyFx.UI 
{

	public class Parameter : Freezable, IAttachedObject
	{
		/// <summary>
		///		the associated object reciever as of this parameter .
		/// </summary>
		private DependencyObject _associatedObject;
		
		/// <summary>
		///		the owner of this parameter .
		/// </summary>
		private WeakReference _ownerObject;


		/// <summary>
		/// A dependency property representing the parameter's value.
		/// </summary>
		public static readonly DependencyProperty ValueProperty =
			DependencyProperty.Register( "Value", typeof(object), typeof(Parameter), new PropertyMetadata(OnValueChanged) );

		

		/// <summary>
		///		Gets or sets the value of the parameter.
		/// </summary>
		[Category("Common Properties")]
		public object Value
		{
			get { 
				return GetValue(ValueProperty); 
			}
			set { 
				SetValue(ValueProperty, value); 
			}
		}

		DependencyObject IAttachedObject.AssociatedObject
		{
			get
			{
				ReadPreamble();
				return this._associatedObject;
			}
		}

		/// <summary>
		/// Gets or sets the owner.
		/// </summary>
		protected MessageAction OwnerObject
		{
			get {
				return _ownerObject == null 
						? null 
						: _ownerObject.Target as MessageAction;
			}
			set { 
				this._ownerObject = new WeakReference(value); 
			}
		}

		void IAttachedObject.Attach ( DependencyObject dependencyObject )
		{
			WritePreamble();
				this._associatedObject = dependencyObject;
			WritePostscript();
		}

		void IAttachedObject.Detach ()
		{
			WritePreamble();
				this._associatedObject = null;
			WritePostscript();
		}

		/// <summary>
		/// 
		/// </summary>
		protected override Freezable CreateInstanceCore()
		{
			return new Parameter();
		}

		/// <summary>
		///		
		/// </summary>
		protected override void CloneCore ( Freezable sourceFreezable)
		{
			if (sourceFreezable is Parameter)
			{
				base.CloneCore(sourceFreezable);
			}
			else
			{
 				throw new System.ArgumentException ( "Clone from non-paramter object .");
			}
		}

		/// <summary>
		///		Makes the parameter aware of the <see cref="MessageAction"/> that it's attached to.
		/// </summary>
		internal void MakeAwareOf( MessageAction ownerObject )
		{
			this.OwnerObject = ownerObject;
		}

		static void OnValueChanged( DependencyObject d, DependencyPropertyChangedEventArgs e )
		{
			var parameter = (Parameter)d;
			var owner = parameter.OwnerObject;

			if ( owner != null )
			{
				owner.NotifyAvailabilityChanged ();
			}
		}
	}



   
}